#!/usr/bin/env python

#################################################################################
#
# Copyright (c) 2006 Michigan State University
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
#################################################################################

#################################################################################
#
#	Author:
#		Nathan Collins <npcollins@gmail.com>
#
#################################################################################

import sys
import MySQLdb
import re
import md5

# unrecoverable error, exit
def err_exit(err_msg):
	print "ERROR: " + err_msg
	sys.exit(0)

# simple all in one query
def quick_query(query_string):
	db = oai_db()
	db.connect()
	retDict = db.query_dict(query_string)
	db.disconnect()
	return retDict

# simple query with no return
def quick_noret(query_string):
	db = oai_db()
	db.connect()
	db.query(query_string)
	db.disconnect()

# global db connection
gdb = None

# connect to the database
class oai_db:
	def __init__(self):
		self.silent = 0
		
		self.hostname = 'localhost'
		self.db_name = 'oaidb'
		self.username = 'oaiuser'
		self.userpass = 'oaipw'

	def connect(self):
		global gdb

		try:
			if gdb == None:
				gdb = MySQLdb.connect(
					host = self.hostname,
					user = self.username,
					passwd = self.userpass,
					db = self.db_name,
					use_unicode = True )
			self.handler = gdb.cursor()
		except:
			err_exit("Could not connect to the database")

	def disconnect(self, globalDisc = 0):
		global gdb
		# disconnect if flag passed and gdb is defined
		if globalDisc != 0 and gdb != None:
			self.handler.close()
			gdb.close()

	def handle(self):
		return self.handler

	def setsilent(self, s = 1):
		# on error, raise exception but do not print anything
		self.silent = s

	def query(self, query_string, args = None):
		try:
			if args == None:
				self.rows = self.handler.execute(query_string)
			else:
				self.rows = self.handler.execute(query_string,args)
				
			# if nothing was returned
			if self.rows < 1:
				return None,None
		except:
			if self.silent == 1:
				raise
			else:
				err_exit("Could not execute query.")
		else:
			self.result = self.handler.fetchall()
			self.fields = self.handler.description
			return self.fields, self.result

	def query_args(self, query_string, val_tuple):
		return self.query(query_string, val_tuple)

	def query_dict(self, query_string):
		"""
		Perform a query and return the results as a list of dicts.
		"""
		retDict = []
		(fields,rows) = self.query(query_string)
		if rows != None:
			# get field names
			dKeys = [field[0] for field in fields]
			
			for row in rows:
				retDict.append( dict(zip(dKeys,row)) )

		return retDict

	def insert(self, table, dictFields):
		"""
		Perform an insert query inserting the dictionary dictFields into table.
		"""
		keys = []
		vals = []

		for k,v in dictFields.iteritems():
			keys.append(k)
			vals.append(v)

		fields = ''
		values = ''

		for k in keys:
			if fields == '':
				fields += k
				values += '%s'
			else:
				fields += ',' + k
				values += ',%s'

		queryStr = 'INSERT INTO %s (%s) VALUES (%s);' % (table, fields, values)

		valTuple = tuple(vals)

		self.query_args(queryStr, valTuple)


# function for generating a hash - MD5
def make_hash(unhashed):
	hashed = md5.new()
	hashed.update(unhashed)
	return hashed.hexdigest()

# filter string, escaping for entry in mysql
class escape_mysql:
	def __init__(self, unescaped = ''):
		self.escaper1 = re.compile(r'\\')
		self.escaper2 = re.compile(r'\'')
		self.escaper3 = re.compile(r'%')
		self.escaper4 = re.compile(r'"')
		if len(unescaped) > 0:
			return self.escape(unescaped)

	def escape(self,unescaped):
		if len(unescaped) < 1:
			return ''
		escaped = self.escaper1.sub(r'\\\\',unescaped)
		escaped = self.escaper2.sub(r'\'',escaped)
		escaped = self.escaper3.sub(r'\%',escaped)
		escaped = self.escaper4.sub(r'\"',escaped)
		return escaped

# eof
